﻿using System;
using System.Collections;
using System.Collections.Generic;

namespace TaskBoardProject
{
    public class TaskBoard :  IEnumerable <Task>, IDisposable
    {
        // List is best collection for this task
        private List <Task> tasks;

        public TaskBoard ()
        {
            tasks = new List <Task>();
        }

        /// <summary>
        ///  The indexer, which will allow to use [] notation
        /// </summary>
        /// <param name="i">index</param>
        /// <returns>Task</returns>
        public Task this[int i]
        {
            get
            {
                return tasks[i];
            }
            set
            {
                tasks[i] = value;
            }
        }

        /// <summary>
        /// Returns generic Enumerator 
        /// </summary>
        /// <returns></returns>
        public IEnumerator <Task> GetEnumerator ()
        {
            return tasks.GetEnumerator();
        }
        
        /// <summary>
        /// Returns non-generic Enumerator 
        /// </summary>
        /// <returns></returns>
        IEnumerator IEnumerable.GetEnumerator()
        {
            return tasks.GetEnumerator();
        }

        /// <summary>
        /// Adds a new Task to TaskBoard
        /// </summary>
        /// <param name="item">Task that you want to add</param>
        public void Add (Task item)
        {
            tasks.Add(item);
        }

        /// <summary>
        /// Removes Task from TaskBoard
        /// </summary>
        /// <param name="item">Task that needs to be removed</param>
        public void Remove (Task item)
        {
            tasks.Remove(item);
        }

        /// <summary>
        /// Removes item at index from TaskBoard
        /// </summary>
        /// <param name="index">Index of the task that needs to be removed</param>
        public void RemoveByIndex (int index)
        {
            tasks.RemoveAt(index);
        }

        /// <summary>
        /// Removes all Tasks from TaskBoard
        /// </summary>
        public void Clear()
        {
            tasks.Clear();
        }


        /// <summary>
        /// Implementation of IDisposable interface.
        /// Here is only Dispose() method, because
        /// class have just managed resources
        /// </summary>
        public void Dispose()
        {
            if (this.tasks != null)
            {
                this.tasks.Clear();
                this.tasks = null;
            }
        }

        public override string ToString()
        {
            return String.Format("This board has {0} tasks. To show details call ToString for elements using index []",tasks.Count);
        }

        public override bool Equals(object obj)
        {
            if (obj != null && obj is TaskBoard)
            {
                TaskBoard compareBoard = (TaskBoard)obj;
                if (this.tasks.Count == compareBoard.tasks.Count)
                {
                    for (int i = 0; i < tasks.Count; i++)
                    {
                        if (!(compareBoard.tasks[i].Equals(this.tasks[i])))
                        {
                            return false;
                        }
                    }
                    return true;
                }
            }
            return false;
        }

        public override int GetHashCode()
        {
            int resultBoardHashCode=0;
            foreach (Task task in tasks)
            {
                resultBoardHashCode ^= task.GetHashCode();
            }
            return resultBoardHashCode;
        }


        ///// <summary>
        ///// Overrided operator == for TaskBoard
        ///// </summary>
        ///// <param name="firstTaskBoard">first task board</param>
        ///// <param name="secondTaskBoard">second task board</param>
        ///// <returns>Return true if first board equals to second board; false if  first board doesn't equals to board</returns>
        //public static bool operator == (TaskBoard firstTaskBoard, TaskBoard secondTaskBoard)
        //{
        //    return firstTaskBoard.Equals(secondTaskBoard);
        //}

        ///// <summary>
        ///// Overrided operator != for TaskBoard
        ///// </summary>
        ///// <param name="firstTaskBoard">first task board</param>
        ///// <param name="secondTaskBoard">second task board</param>
        ///// <returns>Return false if first board equals to second board; true if  first board doesn't equals to board</returns>
        //public static bool operator != (TaskBoard firstTaskBoard, TaskBoard secondTaskBoard)
        //{
        //    return !firstTaskBoard.Equals(secondTaskBoard);
        //}
    }
}
